package _543cloud_new;

import java.io.BufferedReader;
import java.io.FileReader;
import java.io.IOException;
import java.util.ArrayList;
import java.util.Comparator;
import java.util.HashMap;
import java.util.Iterator;
import java.util.PriorityQueue;


public class Graph {
	
	static int MAXVALUE=1<<20;
	static int QUEUELENGTH = 10000;
	
	int[][] weight = new int[QUEUELENGTH][QUEUELENGTH]; // Requestor-->Helper 
	
	PriorityQueue<Left_node> lnode_queue = new PriorityQueue<>(QUEUELENGTH, new lNodeComparator()); 
	PriorityQueue<Right_node> rnode_queue = new PriorityQueue<>(QUEUELENGTH, new rNodeComparator()); 
	HashMap<String,Left_node> lnodes = new HashMap<>();
	HashMap<String,Right_node> rnodes = new HashMap<>();
	HashMap<Integer, String> lnodes_name = new HashMap<>();
	HashMap<Integer, String> rnodes_name = new HashMap<>();
	HashMap<String, Integer> lnodes_num = new HashMap<>();
	HashMap<String, Integer> rnodes_num = new HashMap<>();
	
	public Graph(){
		
	}
	
	public Graph(String args1, String args2) throws IOException{
		getcapcity(args1);
		getedge(args2);
		getnumber();
		getWeightMatrix();
	}
	
	public class lNodeComparator implements Comparator<Left_node> {
		public int compare(Left_node x, Left_node y) {
			if (x.cap < y.cap)
				return -1;
			if (x.cap > y.cap)
				return 1;
			return 0;
		}
	}
	
	public class rNodeComparator implements Comparator<Right_node> {
		public int compare(Right_node x, Right_node y) {
			if (x.cap < y.cap)
				return -1;
			if (x.cap > y.cap)
				return 1;
			return 0;
		}
	}
	
	public void getcapcity(String args) throws IOException{
		BufferedReader br = new BufferedReader(new FileReader(args));
		String temp;
 		while((temp=br.readLine())!=null){
 			String[] to_write = temp.split(",");
 			if(to_write[0].charAt(0)=='l'){
 				Left_node templeft = new Left_node(to_write[0],Integer.parseInt(to_write[1]));
 				lnodes.put(to_write[0], templeft);
 			}
 			if(to_write[0].charAt(0)=='r'){
 				Right_node tempright = new Right_node(to_write[0],Integer.parseInt(to_write[1]));
 				rnodes.put(to_write[0], tempright);
 			}			
 		}
 		br.close();
	}
	
	public void getedge(String args) throws IOException{
		BufferedReader br = new BufferedReader(new FileReader(args));
		String temp;
		while((temp=br.readLine())!=null){
			String[] to_write = temp.split(",");
			if(to_write[0].charAt(0)=='l'){
				Left_node templeft = lnodes.get(to_write[0].trim());
				Right_node tempright = rnodes.get(to_write[1].trim());			
				templeft.neighbor(tempright);
				if(templeft.cap<=tempright.cap){
					templeft.neighbor_available(tempright);
					tempright.neighbor_available(templeft);
					lnodes.put(to_write[0].trim(),templeft);
					rnodes.put(to_write[1].trim(), tempright);
				}
			}
			
			if(to_write[0].charAt(0)=='r'){
				Left_node templeft = lnodes.get(to_write[1].trim());
				Right_node tempright = rnodes.get(to_write[0].trim());
				templeft.neighbor(tempright);
				if(templeft.cap<=tempright.cap){
					templeft.neighbor_available(tempright);
					tempright.neighbor_available(templeft);
					lnodes.put(to_write[1].trim(),templeft);
					rnodes.put(to_write[0].trim(), tempright);
				}
			}
		}
		br.close();
		
		Iterator<Left_node> itr_l = lnodes.values().iterator();
		Iterator<Right_node> itr_r = rnodes.values().iterator();
		while(itr_l.hasNext()){
			lnode_queue.add(itr_l.next());
		}
		while(itr_r.hasNext()){
			rnode_queue.add(itr_r.next());
		}
		
	}
	
	public void getnumber(){
		int l = 0,r=0;
		while(!lnode_queue.isEmpty()){
			Left_node tempL = lnode_queue.poll();
			lnodes_name.put(l, tempL.name);
			lnodes_num.put(tempL.name, l++);
		}
		while(!rnode_queue.isEmpty()){
			Right_node tempR = rnode_queue.poll();
			rnodes_name.put(r,tempR.name);
			rnodes_num.put(tempR.name, r++);
		}
		
		Iterator<Left_node> itr_l = lnodes.values().iterator();
		Iterator<Right_node> itr_r = rnodes.values().iterator();
		while(itr_l.hasNext()){
			lnode_queue.add(itr_l.next());
		}
		while(itr_r.hasNext()){
			rnode_queue.add(itr_r.next());
		}
	}
	
	public void getWeightMatrix(){
		int n = Math.max(lnodes.size(), rnodes.size());
		weight = new int[n][n];
		
		for(int i = 0; i<n; ++i)
			for(int j=0;j<n;++j)
				weight[i][j] = 0;
		
		for(int i=0;i<lnodes.size();i++){
			Left_node templ = lnodes.get(lnodes_name.get(i));
			ArrayList<Right_node> temp_r_list = templ.l_r;
			int leftcap = templ.cap;
					
			for(int k = 0; k< temp_r_list.size() ;k++){
				int rr = rnodes_num.get(temp_r_list.get(k).name);
				weight[i][rr] = Math.min(leftcap, temp_r_list.get(k).cap);
			}	
		}
	}
	
	
	

	/**
	 * For test.
	 */
	public static void main(String[] args){
		try {
			Graph test= new Graph("src/_543cloud_new/capacity.txt", "src/_543cloud_new/relation.txt");
		} catch (IOException e) {
			// TODO Auto-generated catch block
			e.printStackTrace();
		}
		
	}
}
